home *** CD-ROM | disk | FTP | other *** search
- // Header files we may need.
- #include <Finder.h>
- #include <Folders.h>
- #include <Gestalt.h>
- #include <OSUtils.h>
- #include <Packages.h>
- #include <Traps.h>
-
- #include "FilePatches.h"
-
- #ifndef powerc
- #ifdef THINK_C
- #pragma parameter __D0 SetA4(__D0)
- pascal long SetA4(long newA4) = 0xC18C;
-
- #define SetCurrentA4() SetA4((long)&main)
- #else
- #include <A4Stuff.h>
- #endif
- #else
- #define SetCurrentA4() 0
- #define SetA4(x) 0
-
- ProcInfoType __procinfo = kCStackBased
- | RESULT_SIZE(kNoByteCode);
-
- ProcInfoType uppPBFileProcInfo = kRegisterBased
- | RESULT_SIZE( kTwoByteCode )
- | REGISTER_RESULT_LOCATION( kRegisterD0 )
- | REGISTER_ROUTINE_PARAMETER( 1, kRegisterA0, kFourByteCode );
-
- #endif
-
-
- /**************************
- main
- **************************/
-
- void main( void )
- {
- long oldA4;
- long sysVersion;
- OSErr theError;
- THz oldZone;
-
- #ifdef powerc
- UniversalProcPtr newPBHCreateAsyncAddress;
-
- UniversalProcPtr newPBHCreateSyncAddress;
- #endif
-
- // Set up A4, so we can access our globals.
- oldA4 = SetCurrentA4();
-
- oldZone = GetZone();
- SetZone( SystemZone() );
-
- // We need to detach our code, so that we stay around.
- DetachResource( GetResource( INIT_RES_TYPE, BASE_RES_ID ) );
-
- Gestalt( gestaltSystemVersion, &sysVersion );
-
- // We require System 7.
- if ( sysVersion >= MIN_SYSTEM_VERSION )
- {
- gParamBlockCopy = ( HParmBlkPtr )NewPtr( sizeof( HFileParam ) );
- if ( gParamBlockCopy == NIL )
- goto justExit;
-
- gTempStringPtr = ( StringPtr )NewPtr( STRING_LENGTH );
- if ( gTempStringPtr == NIL )
- goto justExit;
-
- #ifndef powerc
- // Register our Gestalt routine, so the backgrounder can call in.
- theError = NewGestalt( FS_SIGNATURE, ( SelectorFunctionUPP )DoFSPatchGestalt );
- #else
- myGestaltUPP = NewSelectorFunctionProc( DoFSPatchGestalt );
- theError = NewGestalt( FS_SIGNATURE, myGestaltUPP );
- #endif
-
- if ( theError != noErr )
- goto justExit;
-
- gFSPatchProcPtr = ( ProcPtr )&DoFSPatchGestalt;
-
- // Standard patch stuff.
- oldPBHCreateSyncAddress = ( PBHProc ) ( ( long )GetOSTrapAddress( _PBHCreateSync ) );
-
- #ifndef powerc
- SetOSTrapAddress( ( UniversalProcPtr )MyPBHCreateAsync, _PBHCreateSync );
- #else
- newPBHCreateSyncAddress = NewRoutineDescriptor( ( ProcPtr )&MyPBHCreateSync, uppPBFileProcInfo, GetCurrentISA() );
- if ( newPBHCreateSyncAddress == 0 )
- goto justExit;
-
- SetOSTrapAddress( newPBHCreateSyncAddress, _PBHCreateSync );
- #endif
- }
-
- justExit:
- // Restore the old zone again
- SetZone(oldZone);
-
- // Required teardown.
- SetA4(oldA4);
- }
-
-
- /**************************
- MyPBHCreateSync
- **************************/
-
- #ifndef powerc
- asm void MyPBHCreateSync( HParmBlkPtr paramBlock )
- {
- MacroPreProcess
-
- move.w kPBHCreateSync, -( sp );
-
- MacroSaveValues
-
- move.l oldPBHCreateSyncAddress, a1;
-
- MacroCallOriginalTrap
- }
- #else
- OSErr MyPBHCreateSync( HParmBlkPtr paramBlock )
- {
- OSErr theResult;
-
- CopyHParamBlockValues( paramBlock, kPBHCreateSync );
-
- theResult = CallOSTrapUniversalProc( ( UniversalProcPtr )oldPBHCreateSyncAddress, uppPBFileProcInfo, paramBlock );
-
- if ( theResult == noErr )
- SetArrayElement();
-
- return theResult;
- }
- #endif
-
-
- /**************************
- CopyHParamBlockValues
- **************************/
-
- void CopyHParamBlockValues( HParmBlkPtr paramBlock, short theTrapId )
- {
-
- #ifdef __DEBUG__
- DebugStr( "\pInside CopyHParamBlockValues()..." );
- #endif
-
- // Is this field valid?
- gParamBlockCopy->fileParam.ioTrap = paramBlock->fileParam.ioTrap;
-
- gParamBlockCopy->fileParam.ioTrap = theTrapId;
- gParamBlockCopy->fileParam.ioVRefNum = paramBlock->fileParam.ioVRefNum;
- gParamBlockCopy->fileParam.ioDirID = paramBlock->fileParam.ioDirID;
- gParamBlockCopy->fileParam.ioFlFndrInfo.fdType = paramBlock->fileParam.ioFlFndrInfo.fdType;
- gParamBlockCopy->fileParam.ioNamePtr = paramBlock->fileParam.ioNamePtr;
- }
-
-
- /**************************
- SetArrayElement
- **************************/
-
- void SetArrayElement( void )
- {
- short count = 0, max = 0;
- FSPatchGlobalsPtr paramBlockCopy = nil;
- FWData theFWData;
-
- #ifdef __DEBUG__
- short trap = 0;
- #endif
-
- SendAppleEvent();
-
- theFWData.theTrapId = gParamBlockCopy->fileParam.ioTrap;
- theFWData.theVRefNum = gParamBlockCopy->fileParam.ioVRefNum;
- theFWData.theParID = gParamBlockCopy->fileParam.ioDirID;
- theFWData.theFileType = gParamBlockCopy->fileParam.ioFlFndrInfo.fdType;
-
- count = 0;
- max = gParamBlockCopy->fileParam.ioNamePtr[ 0 ];
-
- while ( count <= max ) {
- theFWData.theString[ count ] = gParamBlockCopy->fileParam.ioNamePtr[ count ];
- count++;
- }
-
- #ifdef __DEBUG__
- DebugStr( "\pInside SetArrayElement()..." );
- #endif
-
- #ifdef __DEBUG__
- trap = gParamBlockCopy->fileParam.ioTrap;
- #endif
-
- // if ( gCallbackProcPtr != 0L ) {
- if ( ( gParamBlockCopy->fileParam.ioTrap == 0xFFFFA208 ) && gCallbackProcPtr != 0L ) {
- #ifdef __DEBUG__
- DebugStr( "\pCalling callback from patch..." );
- #endif
- CallUniversalProc( gCallbackProcPtr, uppCreateFileProcInfo, theFWData );
- }
-
- // Added by ASD on 01/28/99.
- // Get next free element.
- // If it doesn't exist, get out.
- paramBlockCopy = ( FSPatchGlobalsPtr )PopAtomicStack( &gInputStack );
- if ( !paramBlockCopy )
- return;
-
- // Copy PBRec data to new element.
- // Don't forget the trap id.
- paramBlockCopy->theTrapId = gParamBlockCopy->fileParam.ioTrap;
- paramBlockCopy->theVRefNum = gParamBlockCopy->fileParam.ioVRefNum;
- paramBlockCopy->theParID = gParamBlockCopy->fileParam.ioDirID;
- paramBlockCopy->theFileType = gParamBlockCopy->fileParam.ioFlFndrInfo.fdType;
-
- // Save the Str255 temporary parameter copy.
- count = 0;
- max = gParamBlockCopy->fileParam.ioNamePtr[ 0 ];
-
- while ( count <= max ) {
- paramBlockCopy->theString[ count ] = gParamBlockCopy->fileParam.ioNamePtr[ count ];
- count++;
- }
- }
-
-
- /**************************
- SendAppleEvent
- **************************/
-
- void SendAppleEvent( void )
- {
- AEAddressDesc theAddressDesc;
- AppleEvent theAppleEvent, theReply;
- Boolean foundBackgroundApp;
- FSSpec theSpec;
- OSErr theError;
- ProcessInfoRec InfoRec;
- ProcessSerialNumber thePSN, *myPtr;
- Str32 theName;
-
- foundBackgroundApp = false;
- InfoRec.processInfoLength = sizeof( ProcessInfoRec );
- InfoRec.processName = theName;
- InfoRec.processAppSpec = &theSpec;
-
- thePSN.highLongOfPSN = 0;
- thePSN.lowLongOfPSN = kNoProcess;
-
- while ( GetNextProcess( &thePSN ) != procNotFound )
- {
- theError = GetProcessInformation( &thePSN, &InfoRec );
- if ( InfoRec.processSignature == 'asd9' )
- {
- foundBackgroundApp = true;
- break;
- }
- }
-
- theError = FSMakeFSSpec( gParamBlockCopy->fileParam.ioVRefNum, gParamBlockCopy->fileParam.ioDirID, gParamBlockCopy->fileParam.ioNamePtr, &theSpec );
-
- if ( theError != noErr ) {
- #ifdef __DEBUG__
- DebugStr( "\pUnable to create FSSpec in Extension." );
- #endif
- return;
- }
-
- if ( foundBackgroundApp )
- {
- myPtr = &thePSN;
-
- theError = AECreateDesc( typeProcessSerialNumber, ( Ptr )myPtr, sizeof( ProcessSerialNumber ), &theAddressDesc );
-
- theError = AECreateAppleEvent( 'asd9', 'newf', &theAddressDesc, kAutoGenerateReturnID, kAnyTransactionID, &theAppleEvent );
-
- theError = AEPutParamPtr( &theAppleEvent, keyDirectObject, typeFSS, &theSpec, sizeof( FSSpec ) );
-
- theError = AESend( &theAppleEvent, &theReply, kAENoReply, kAENormalPriority, kNoTimeOut, NIL, NIL );
-
- theError = AEDisposeDesc( &theAddressDesc );
- theError = AEDisposeDesc( &theAppleEvent );
- }
- }
-
-
- /**************************
- DoFSPatchGestalt
- **************************/
-
- static pascal OSErr DoFSPatchGestalt( OSType theSelector, long *theResponse )
- {
- short theAction;
- long oldA4;
- OSErr theError = noErr;
-
- // Set up A4, so we can access our globals.
- oldA4 = SetCurrentA4();
-
- // The caller must request a specific selector when calling our Gestalt routine.
- switch ( theSelector )
- {
- case GESTALT_GET_INIT_GLOBALS:
- // Return the address of the array.
- *theResponse = ( long )&gFSPatchGlobals;
- break;
-
- case GESTALT_GET_ONE_GLOBALS:
- // Return the next array element.
- *theResponse = ( long )&gFSPatchGlobals[ gLastRetrievedElement ];
-
- // Update the index to the next element to send to the user.
- gLastRetrievedElement++;
-
- if ( gLastRetrievedElement > MAX_NUM_FILES - 1 )
- gLastRetrievedElement = 0;
-
- break;
-
- case FS_SIGNATURE:
- // Return the address of this function.
- #ifndef powerc
- *theResponse = ( long )gFSPatchProcPtr;
- #else
- *theResponse = ( long )myGestaltUPP;
- #endif
- break;
-
- case gestaltVersion:
- // Return the version of this INIT.
- *theResponse = FS_VERSION_CURRENT;
- break;
-
- case GESTALT_ADD_CALLBACK:
- #ifdef __DEBUG__
- DebugStr( "\pCreating Routine Descriptor in DoFSPatchGestalt()..." );
- #endif
- theAction = ( ( FWSubscribePtr )theResponse )->theAction;
- switch ( theAction ) {
- case kCreateFlag:
- gCallbackProcPtr = NewRoutineDescriptor( ( ProcPtr )( ( FWSubscribePtr )theResponse )->theCallbackAddr, uppCreateFileProcInfo, kPowerPCISA );
- break;
-
- default:
- break;
- }
-
- break;
-
- case GESTALT_REMOVE_CALLBACK:
- #ifdef __DEBUG__
- DebugStr( "\pRemoving Routine Descriptor in DoFSPatchGestalt()..." );
- #endif
- theAction = ( ( FWSubscribePtr )theResponse )->theAction;
- switch ( theAction ) {
- case kCreateFlag:
- if ( gCallbackProcPtr->routineRecords[ 0 ].procDescriptor == ( ProcPtr )( ( FWSubscribePtr )theResponse )->theCallbackAddr ) {
- #ifdef __DEBUG__
- DebugStr( "\pGracefully removing Routine Descriptor in DoFSPatchGestalt()..." );
- #endif
- DisposeRoutineDescriptor( ( UniversalProcPtr )gCallbackProcPtr );
- gCallbackProcPtr = nil;
- }
-
- break;
-
- default:
- break;
- }
-
- break;
-
- default:
- // Don't understand the request.
- theError = gestaltUnknownErr;
- break;
- }
-
- // Required teardown.
- SetA4(oldA4);
-
- return( theError );
- }
-
-
-